import axios from "axios";
import { Message } from "element-ui";
import { getCache } from "@/utils/session";
import globalConfig from "../../global.config";
import router from "@/router";
import store from '@/store';
import CryptoJS from 'crypto-js';
import qs from "qs";
// 配置全局的基础配置
const service = axios.create({
  baseURL: "http://localhost:5000",//TODO: 配置全局的基础地址
  timeout: 5000,
  headers: {
    // "Content-Type": "application/json;charset=utf-8",
  },
});

// 添加请求拦截器
// 1、添加token
//    如果url不在白名单中且没有token则设置token
// 2、设置白名单whiteList
// 3、设置密钥,加到请求头中
// 避免请求伪造，通过secretId + MD5算法，保障请求通过项目发送
service.interceptors.request.use(
  (config)=> {
    let whiteList = globalConfig.whiteListApi;
    let url = config.url;
    //  || getCache("TOKEN");
    let token = store.getters.token || getCache('TOKEN')
    if(whiteList.indexOf(url) === -1 && token) {
      // TODO：这里需要确定token存储位置
      config.headers['Authorization'] = token;
    }

    let _secret = globalConfig.secretId + new Date() + toString();
    config.headers['secret'] = CryptoJS.MD5(_secret).toString();;

    return config;
  },
  (error)=> {
    console.log('request- error', error);
    return Promise.reject(error);
  }
)
// 响应拦截器
// 1、处理token失效跳转到登录页面
// 2、处理其他错误
service.interceptors.response.use(
  (response)=> {
    const status = response.data.status || 200;
    const message = response.data.message || "请求失败";
    
    // 遇到401状态码时，常见的做法是重定向到登录页面，或者弹出登录框要求用户重新登录。
    // TODO:状态码统一处理
    if(status === 401) {
      alert("token失效，请重新登录");
      
      router.push("/login");
      return Promise.reject(new Error(message));
    }

    if(status !== 200) {
      Message({
        message: message,
        type: "error",
        duration: 5 * 1000,
      });
      return Promise.reject(new Error(message));
    }
    return response;
  },
  (error) => {
    // 响应出错如何处理
    Message.error("请求出错：" + error.response.data.message);
    return Promise.reject(new Error(error));
  }
)


let http = {};
/**
 * get方法，对应get请求
 * @param {String} url [请求的url地址]
 * @param {Object} params [请求时携带的参数]
 */

http.get = function (url, params = null) {
  return new Promise((resolve, reject) => {
    service
      .get(url, { params })
      .then(res => {
        resolve(res.data);
      })
      .catch(e => {
        reject(e);
      });
  });
};

/**
 * post方法，对应post请求
 * @param {String} url [请求的url地址]
 * @param {Object} params [请求时携带的参数]
 */

http.post = function (url, params) {
  return new Promise((resolve, reject) => {
    service
      .post(url, qs.stringify(params))
      .then(res => {
        resolve(res.data);
      })
      .catch(e => {
        reject(e);
      });
  });
};

export default http;